package com.ice.base.util;

import com.arcsoft.face.*;
import com.arcsoft.face.enums.DetectMode;
import com.arcsoft.face.enums.DetectOrient;
import com.arcsoft.face.enums.ErrorInfo;
import com.arcsoft.face.toolkit.ImageInfo;
import com.ice.base.model.SysLoginModel;
import com.ice.base.service.ParamService;
import com.ice.base.service.SysLoginService;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

import java.io.File;
import java.util.ArrayList;
import java.util.List;

import static com.arcsoft.face.toolkit.ImageFactory.getRGBData;

@Component
public class FaceEngineTool {

	//从官网获取
    static String appId = "HD15ogKz2RuBXTAjZh2xQjcmu6HQ2YwnaGksQs9RCnN9";
    static String sdkKey = "ArpLLbri5PWoZmVUYFur8VPWQ5cgjheH8CwKj2WEmTtJ";
 	static FaceEngine faceEngine = null;
    static int errorCode=0;

    @Autowired
    private SysLoginService sysLoginService;

    @Autowired
    private ParamService paramService;

    @Autowired
    private RedisUtil redisUtil;

    public void init(){
        if(null == faceEngine){
            faceEngine = new FaceEngine("D:\\soft\\arcSoft");
        }
        //激活引擎
        String appId = paramService.getValueByKey("appId");
        String sdkKey = paramService.getValueByKey("sdkKey");
        errorCode = faceEngine.activeOnline(appId, sdkKey);

        if (errorCode != ErrorInfo.MOK.getValue() && errorCode != ErrorInfo.MERR_ASF_ALREADY_ACTIVATED.getValue()) {
            System.out.println("引擎激活失败,错误码："+errorCode);
        }


        ActiveFileInfo activeFileInfo=new ActiveFileInfo();
        errorCode = faceEngine.getActiveFileInfo(activeFileInfo);
        if (errorCode != ErrorInfo.MOK.getValue() && errorCode != ErrorInfo.MERR_ASF_ALREADY_ACTIVATED.getValue()) {
            System.out.println("获取激活文件信息失败,错误码："+errorCode);
        }

        //引擎配置
        EngineConfiguration engineConfiguration = new EngineConfiguration();
        engineConfiguration.setDetectMode(DetectMode.ASF_DETECT_MODE_IMAGE);
        engineConfiguration.setDetectFaceOrientPriority(DetectOrient.ASF_OP_ALL_OUT);
        engineConfiguration.setDetectFaceMaxNum(10);
        engineConfiguration.setDetectFaceScaleVal(16);
        //功能配置
        FunctionConfiguration functionConfiguration = new FunctionConfiguration();
        functionConfiguration.setSupportAge(true);
        functionConfiguration.setSupportFace3dAngle(true);
        functionConfiguration.setSupportFaceDetect(true);
        functionConfiguration.setSupportFaceRecognition(true);
        functionConfiguration.setSupportGender(true);
        functionConfiguration.setSupportLiveness(true);
        functionConfiguration.setSupportIRLiveness(true);
        engineConfiguration.setFunctionConfiguration(functionConfiguration);


        //初始化引擎
        errorCode = faceEngine.init(engineConfiguration);

        if (errorCode != ErrorInfo.MOK.getValue()) {
            System.out.println("虹软-初始化引擎失败，错误码："+errorCode);
        }
    }
 	


	public FaceEngineTool(){

	}

 	/**
 	 * 对比人脸 获取结果
 	 * */
	public  float CheckFace(FaceFeature ffa,FaceFeature ffb) {
		
        //特征比对
        FaceFeature targetFaceFeature = new FaceFeature();
        targetFaceFeature.setFeatureData(ffa.getFeatureData());
        FaceFeature sourceFaceFeature = new FaceFeature();
        sourceFaceFeature.setFeatureData(ffb.getFeatureData());
        FaceSimilar faceSimilar = new FaceSimilar();
        errorCode = faceEngine.compareFaceFeature(targetFaceFeature, sourceFaceFeature, faceSimilar);
        //System.out.println("相似度：" + faceSimilar.getScore());
        return faceSimilar.getScore();
       
	}     
	     
	
	/**
	 * 根据地址获取人脸特征
	 * */	
	public FaceFeature pathGetFace(String path) {
		//人脸检测
		File file=new File(path);
		if(!file.exists()){
		    return new FaceFeature();
        }
        ImageInfo imageInfo = getRGBData(file);
        List<FaceInfo> faceInfoList = new ArrayList<>();
        errorCode = faceEngine.detectFaces(imageInfo.getImageData(), imageInfo.getWidth(), imageInfo.getHeight(), imageInfo.getImageFormat(), faceInfoList);
        //System.out.println(faceInfoList);
        FaceFeature faceFeature = new FaceFeature();
        //特征提取
        if(faceInfoList.size() > 0){
            errorCode = faceEngine.extractFaceFeature(imageInfo.getImageData(), imageInfo.getWidth(), imageInfo.getHeight(), imageInfo.getImageFormat(), faceInfoList.get(0), faceFeature);
            //System.out.println("特征值大小：" + faceFeature.getFeatureData().length);
        }
        return faceFeature;
	}
	
	
	/**
	 * 加载用户 -获取所有人脸特征
	 * */
    public void getFaceFeature(){
        List<SysLoginModel> userList = sysLoginService.selectAll();
        if(null != userList && userList.size() > 0){
            for (SysLoginModel user : userList) {
                if(!redisUtil.hHasKey("faceMap",user.getId().toString())
                        || "".equals(redisUtil.hget("faceMap",user.getId().toString()))){
                    if(StringUtils.isNotEmpty(user.getFacePath())){
                        try{
                            File file=new File(user.getFacePath());
                            if(null == file){
                                continue;
                            }
                            ImageInfo imageInfo = getRGBData(file);
                            List<FaceInfo> faceInfoList = new ArrayList<>();
                            errorCode = faceEngine.detectFaces(imageInfo.getImageData(), imageInfo.getWidth(), imageInfo.getHeight(), imageInfo.getImageFormat(), faceInfoList);
                            System.out.println("ERRORCODE:"+errorCode+"   "+faceInfoList);
                            //特征提取
                            FaceFeature faceFeature = new FaceFeature();
                            if(faceInfoList.size() > 0){
                                errorCode = faceEngine.extractFaceFeature(imageInfo.getImageData(), imageInfo.getWidth(), imageInfo.getHeight(), imageInfo.getImageFormat(), faceInfoList.get(0), faceFeature);
                                System.out.println("ERRORCODE:"+errorCode+"特征值大小" + faceFeature.getFeatureData().length);
                                redisUtil.hset("faceMap",user.getId().toString(),faceFeature);
                            }
                        }catch(Exception e){
                            e.printStackTrace();
                        }
                    }
                }
            }
        }
    }


    /**
	  * 卸载引擎
	  * */
	 public void unitFaceEngine() {
		//引擎卸载
	    errorCode = faceEngine.unInit();
	 }
}